package top.aigoo.project01.controller.shopadmin;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.JsonMappingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.multipart.MultipartHttpServletRequest;
import org.springframework.web.multipart.commons.CommonsMultipartFile;
import org.springframework.web.multipart.commons.CommonsMultipartResolver;
import top.aigoo.project01.entity.Area;
import top.aigoo.project01.entity.PersonInfo;
import top.aigoo.project01.entity.Shop;
import top.aigoo.project01.entity.ShopCategory;
import top.aigoo.project01.entity.dto.ImageHolder;
import top.aigoo.project01.entity.dto.ShopExecution;
import top.aigoo.project01.enums.ShopStateEnum;

import top.aigoo.project01.service.AreaService;
import top.aigoo.project01.service.ShopCategoryService;
import top.aigoo.project01.service.ShopService;
import top.aigoo.project01.utils.CodeUtil;
import top.aigoo.project01.utils.HttpServletRequestUtil;


import javax.servlet.http.HttpServletRequest;
import java.io.*;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * @Description: shop 商店controller接口
 * @Author: Mr.OYSHUO.欧阳大叔  mail:1642302522@qq.com
 * @Version 1.0.0
 * @Date: 2021/8/9 19:23
 */
@Controller
@RequestMapping("/shopadmin")
public class ShopManagementController {
    // 1.定义modelMap封装返回值
    private Map<String, Object> modelMap;

    private final ShopService shopService;
    private final ShopCategoryService shopCategoryService;
    private final AreaService areaService;

    @Autowired
    public ShopManagementController(ShopService shopService, ShopCategoryService shopCategoryService, AreaService areaService) {
        this.shopService = shopService;
        this.shopCategoryService = shopCategoryService;
        this.areaService = areaService;
    }

    /**
     * 直接访问该页面且未经过登录，或者未经过店铺列表连接出来，就重定向到店铺列表，
     * 如果之前已经登录过系统，有权限访问，那就让用用户在这个页面访问
     * 管理session相关的操作,此处会将当前shop放到session的“currentShop”中
     *
     * @param request
     * @return
     */
    @RequestMapping(value = "/getshopmanagementinfo", method = RequestMethod.GET)
    @ResponseBody
    private Map<String, Object> getShopManagementInfo(HttpServletRequest request) {
        // 1.定义modelMap封装返回值
        Map<String, Object> modelMap = new HashMap<>();

        long shopId = HttpServletRequestUtil.getLong(request, "shopId");

        if (shopId <= 0) {
            // 如果url没有shopId
            Object currentShopObj = request.getSession().getAttribute("currentShop");

            if (currentShopObj == null) {
                modelMap.put("redirect", true);
                modelMap.put("url", "/o2o/shopadmin/shoplist");
            } else {
                Shop currentShop = (Shop) currentShopObj;
                modelMap.put("redirect", false);
                modelMap.put("shopId", currentShop.getShopId());
            }
        } else {
            // 如果Url里面有shopId
            Shop currentShop = new Shop();
            currentShop.setShopId(shopId);
            request.getSession().setAttribute("currentShop", currentShop);
            modelMap.put("redirect", false);
        }
        return modelMap;
    }

    /**
     * 查询当前用户创建的店铺列表
     */
    @RequestMapping(value = "/getshoplist", method = RequestMethod.GET)
    @ResponseBody
    private Map<String, Object> getShopList(HttpServletRequest request) {
        // 1.定义modelMap封装返回值
        modelMap = new HashMap<>();
        PersonInfo owner = null;
        //2. 通过session获取用户的信息，实现获取当前用户创建的商店列表
        if (request.getSession().getAttribute("user") == null) {
            //@TODO 没有的话，这个是测试账户，正式上线需要去掉
            owner = new PersonInfo();
            owner.setUserId(1L);
            owner.setName("test");
            owner.setEnableStatus(1);
            request.getSession().setAttribute("user", owner);
        }

        owner = (PersonInfo) request.getSession().getAttribute("user");
        //3.查询shopList并返回前台
        try {
            Shop shopCondition = new Shop();
            shopCondition.setOwner(owner);
            ShopExecution se = shopService.getShopList(shopCondition, 0, 100);

            modelMap.put("success", true);
            modelMap.put("shopList", se.getShopList());
            modelMap.put("user", owner);
            //列出店铺成功后，将店铺放入到session中作为权限验证的依据，及该账号只可以操作他自己的店铺
            request.getSession().setAttribute("shopList", se.getShopList());
        } catch (Exception e) {
            modelMap.put("success", false);
            modelMap.put("errMsg", e.getMessage());
        }
        return modelMap;
    }

    /**
     * 根据shopId查询店铺信息
     *
     * @param request
     * @return
     */
    @RequestMapping(value = "/getshopbyid", method = RequestMethod.GET)
    @ResponseBody
    private Map<String, Object> getShopById(HttpServletRequest request) {
        // 1.定义modelMap封装返回值
        Map<String, Object> modelMap = new HashMap<>();

        // 2.从request中获取shopId
        Long shopId = HttpServletRequestUtil.getLong(request, "shopId");
        //3.开始查询shop
        if (shopId != null && shopId > -1) {
            try {
                Shop shop = shopService.getByShopId(shopId);
                List<Area> areaList = areaService.getAreaList();
                modelMap.put("shop", shop);
                modelMap.put("areaList", areaList);
                modelMap.put("success", true);
            } catch (Exception e) {
                modelMap.put("success", false);
                modelMap.put("errMsg", e.toString());
            }
        } else {
            modelMap.put("success", false);
            modelMap.put("errMsg", "empty shopId! 请携带shopId");
        }
        return modelMap;
    }

    /**
     * 修改店铺
     */
    @RequestMapping(value = "/modifyshop", method = RequestMethod.POST)
    @ResponseBody
    private Map<String, Object> modifyShop(HttpServletRequest request) {
        // 1.定义modelMap封装返回值
        Map<String, Object> modelMap = new HashMap<>();
        //对验证码的校验
        if (!CodeUtil.checkVerifyCode(request)) {
            modelMap.put("success", false);
            modelMap.put("errMsg", "输入了错误的验证码");
            return modelMap;
        }
        //2.接收并转化相应的参数包裹店铺信息以及图片信息
        String shopStr = HttpServletRequestUtil.getString(request, "shopStr");
        ObjectMapper mapper = new ObjectMapper();
        Shop shop = null;
        try {
            shop = mapper.readValue(shopStr, Shop.class);
        } catch (Exception e) {
            modelMap.put("success", false);
            modelMap.put("errMsg", e.getMessage());
            return modelMap;
        }
        //3.从httpServletRequest处理图片信息
        CommonsMultipartFile shopImg = null;
        CommonsMultipartResolver commonsMultipartResolver = new CommonsMultipartResolver(request.getSession().getServletContext());
        /*判断请求中是否有上传文件流*/
        if (commonsMultipartResolver.isMultipart(request)) {
            MultipartHttpServletRequest multipartHttpServletRequest = (MultipartHttpServletRequest) request;
            shopImg = (CommonsMultipartFile) multipartHttpServletRequest.getFile("shopImg");
        }

        //5.修改店铺信息
        if (shop != null && shop.getShopId() != null) {
            ShopExecution se;
            try {
                ImageHolder thumnail = new ImageHolder(shopImg.getOriginalFilename(), shopImg.getInputStream());
                if (shopImg == null) {
                    se = shopService.modifyShop(shop, null);
                } else {
                    se = shopService.modifyShop(shop, thumnail);
                }
                if (se.getState() == ShopStateEnum.SUCCESS.getState()) {
                    modelMap.put("success", true);
                    modelMap.put("errMsg", "创建成功");
                } else {
                    modelMap.put("success", false);
                    modelMap.put("errMsg", se.getStateInfo());
                }
            } catch (Exception e) {
                modelMap.put("success", false);
                modelMap.put("errMsg", e.getMessage());
                return modelMap;
            }
            return modelMap;
        } else {
            modelMap.put("success", false);
            modelMap.put("errMsg", "shopId 不能为空!");
            return modelMap;
        }
        //3.返回结果
    }

    /**
     * 注册店铺
     */
    @RequestMapping(value = "/registershop", method = RequestMethod.POST)
    @ResponseBody
    private Map<String, Object> registerShop(HttpServletRequest request) {
        // 1.定义modelMap封装返回值
        Map<String, Object> modelMap = new HashMap<>();
        // 验证校验码
        if (!CodeUtil.checkVerifyCode(request)) {
            modelMap.put("success", false);
            modelMap.put("errMsg", "输入了错误的验证码");
            return modelMap;
        }

        //1.使用jackson，将string转化为pojo，接收并转化相应的参数包裹店铺信息以及图片信息
        String shopStr = HttpServletRequestUtil.getString(request, "shopStr");
        ObjectMapper mapper = new ObjectMapper();
        Shop shop = null;
        try {
            shop = mapper.readValue(shopStr, Shop.class);
        } catch (Exception e) {
            modelMap.put("success", false);
            modelMap.put("errMsg", e.getMessage());
            return modelMap;
        }
        /*处理图片相关信息*/
        CommonsMultipartFile shopImg = null;
        CommonsMultipartResolver commonsMultipartResolver = new CommonsMultipartResolver(request.getSession().getServletContext());
        /*判断请求中是否有上传文件流*/
        if (commonsMultipartResolver.isMultipart(request)) {
            MultipartHttpServletRequest multipartHttpServletRequest = (MultipartHttpServletRequest) request;
            shopImg = (CommonsMultipartFile) multipartHttpServletRequest.getFile("shopImg");
        } else {
            modelMap.put("success", false);
            modelMap.put("errMsg", "上传图片不能为空");
            return modelMap;
        }
        //2.注册店铺
        if (shop != null && shopImg != null) {
            // 从session读取用户信息
            PersonInfo owner = (PersonInfo) request.getSession().getAttribute("user");
            if (owner == null) {
                modelMap.put("success", false);
                modelMap.put("errMsg", "当前用户信息为空");
                //return modelMap;
                owner = new PersonInfo();
                owner.setUserId(1L);
            }
            shop.setOwner(owner);
            /*File shopImgFile = new File(PathUtil.getImgBasePath() + ImageUtil.getRandomFileName());
            try {
                //shopImgFile.createNewFile();
                inputStreamToFile(shopImg.getInputStream(), shopImg.getInputStream());
            } catch (IOException e) {
                modelMap.put("success", false);
                modelMap.put("errMsg", e.getMessage());
                return modelMap;
            }*/
            ShopExecution se;
            try {
                ImageHolder thumnail = new ImageHolder(shopImg.getOriginalFilename(), shopImg.getInputStream());

                se = shopService.addShop(shop, thumnail);
                if (se.getState() == ShopStateEnum.CHECK.getState()) {
                    modelMap.put("success", true);
                    modelMap.put("errMsg", "创建成功");
                    // 该用户可以操作的店铺列表,把自己注册的店铺放到自己的shopList
                    List<Shop> shopList = (List<Shop>) request.getSession().getAttribute("shopList");

                    if (shopList == null || shopList.size() == 0) {
                        shopList = new ArrayList<>();
                    }
                    shopList.add(se.getShop());
                    request.getSession().setAttribute("shopList", shopList);
                } else {
                    modelMap.put("success", false);
                    modelMap.put("errMsg", se.getStateInfo());
                }
            } catch (Exception e) {
                modelMap.put("success", false);
                modelMap.put("errMsg", e.getMessage());
            }
            return modelMap;
        } else {
            modelMap.put("success", false);
            modelMap.put("errMsg", "请输入店铺信息");
            return modelMap;
        }
        //3.返回结果
    }

    /**
     * 注册页信息初始化接口，初始化areaList和shopCategoryList两个下拉选项
     */
    @RequestMapping(value = "/getshopinitinfo", method = RequestMethod.GET)
    @ResponseBody
    private Map<String, Object> getShopInitInfo() {
        // 1.初始化
        Map<String, Object> modelMap = new HashMap<>();
        List<ShopCategory> shopCategoryList = new ArrayList<ShopCategory>();
        List<Area> areaList = new ArrayList<Area>();
        //2.调用对应的Service获取参数
        try {
            shopCategoryList = shopCategoryService.getShopCategoryList(new ShopCategory());

            areaList = areaService.getAreaList();

            modelMap.put("shopCategoryList", shopCategoryList);
            modelMap.put("areaList", areaList);
            modelMap.put("success", true);
        } catch (Exception e) {
            modelMap.put("success", "false");
            modelMap.put("errMsg", e.getMessage());
        }
        //3.返回结果
        return modelMap;
    }

    /**
     * 将CommonsMultipartFile转换为File
     */
    private static void inputStreamToFile(InputStream ins, File file) {
        OutputStream os = null;
        try {
            os = new FileOutputStream(file);
            int bytesRead = 0;
            byte[] buffer = new byte[1024];
            while ((bytesRead = ins.read(buffer)) != -1) {
                os.write(buffer, 0, bytesRead);
            }
        } catch (FileNotFoundException e) {
            throw new RuntimeException("文件不存在,调用inputStreamToFile异常" + e.getMessage());
        } catch (IOException e) {
            throw new RuntimeException("调用inputStreamToFile异常,读写异常" + e.getMessage());
        } finally {
            try {
                if (os != null) {
                    os.close();
                }
                if (ins != null) {
                    ins.close();
                }
            } catch (IOException e) {
                throw new RuntimeException("调用inputStreamToFile异常,读写异常" + e.getMessage());
            }
        }
    }
}
